你认真的样子真可爱004

您所在的位置:网站首页 include 头文件 知乎 你认真的样子真可爱004

你认真的样子真可爱004

2023-04-09 00:30| 来源: 网络整理| 查看: 265

问题:如何利用GLOB_RECURSE获取APP_HEADER_DIR文件夹内所有子文件夹目录?

可以使用以下代码来利用 GLOB_RECURSE 获取 APP_HEADER_DIR 文件夹内所有子文件夹的目录:

# 设置头文件目录 set(APP_HEADER_DIR /path/to/header/directory) # 获取所有子文件夹目录 file(GLOB_RECURSE HEADER_DIRS ${APP_HEADER_DIR}/*) # 过滤掉非目录路径 foreach(HEADER_DIR ${HEADER_DIRS}) if(NOT IS_DIRECTORY ${HEADER_DIR}) list(REMOVE_ITEM HEADER_DIRS ${HEADER_DIR}) endif() endforeach() # 打印目录路径 message("Header directories: ${HEADER_DIRS}")

说明:

首先,通过

set 命令设置

APP_HEADER_DIR 变量为指定的头文件目录。

接着,使用

file(GLOB_RECURSE) 命令获取所有符合

${APP_HEADER_DIR}/* 模式的文件路径,包括子目录中的文件。这些文件路径将储存在

HEADER_DIRS 变量中。

由于

HEADER_DIRS 变量中可能包含非目录路径,我们需要使用

foreach 循环和

IS_DIRECTORY 函数来过滤掉这些非目录路径。

最后,使用

message 命令来输出

HEADER_DIRS 变量中的目录路径。

问题:include_directories包含的路径可否在编译每一个c文件时不显示?

include_directories指定的路径是为了告诉编译器去哪里查找头文件,因此在编译每一个C文件时都会显示一次包含路径是正常的。如果你不想看到这些信息,可以使用编译器选项-Wno-include-path来关闭这些警告。

例如,在使用GCC编译器时,可以使用以下命令禁用这些警告:

gcc -Wno-include-path -c foo.c

该命令将禁止GCC在编译foo.c时显示include_directories命令指定的包含路径。请注意,这将禁止在所有的C文件中输出相关警告信息。如果您希望在某些C文件中保留这些警告,请移除-Wno-include-path选项并将其加上-Winclude-dirs选项,就可以在需要的情况下显示警告信息和对应的路径了。

问题:include_directories包含的路径为什么在编译每一个c文件时都会显示一次?

include_directories命令可以将指定的路径添加到编译器的包含路径中,以便编译器在编译源码时能够找到相关的头文件,从而成功编译。但是,在编译每个C文件时都会显示一次包含路径,是因为C文件需要被单独地编译为目标文件,而每个C文件都需要被编译成单独的目标文件。因此,在编译每个C文件之前,都需要将相应的包含路径传递给编译器,以便它能够找到所有的头文件。

举个例子,假设有两个C文件foo.c和bar.c,它们都包含相同的头文件myheader.h,而这个头文件在路径/path/to/myheader下。在使用include_directories命令时,我们会将路径/path/to/myheader添加到包含路径中:

include_directories(/path/to/myheader)

在编译时,我们使用如下的指令将这些C文件编译成目标文件:

gcc -c foo.c gcc -c bar.c

编译器在编译foo.c时,需要先搜索包含路径中的/path/to/myheader,以便找到myheader.h,因此会输出一条类似于以下的消息:

In file included from foo.c:1: /path/to/myheader/myheader.h: ...

然后,编译器在编译bar.c时,同样需要搜索包含路径中的/path/to/myheader,所以也会输出类似的消息。

因此,在编译每个C文件时都会显示一次包含路径,这是一种正常的行为,而且也是必要的,因为每个C文件都需要单独编译。

问题:有什么办法可以不让makefile在编译时显示太多的包含路径?

可以通过在Makefile中定义一个特殊的目标来控制打印输出,从而避免在编译时显示太多的包含路径。具体做法如下:

首先,将要隐藏的路径放到一个变量中,比如HIDDEN_PATHS,然后添加一个特殊的目标.SILENT,在这个目标下,将这个变量设置为空字符串,即:

HIDDEN_PATHS = /usr/include/mylibrary .SILENT: HIDDEN_PATHS =

在这个目标下,make不会打印编译器的命令,并且HIDDEN_PATHS变量将被重新赋值为空字符串。然后,将这个变量添加到编译器的参数中,以使得编译器不会显示这些包含路径,比如:

CC = gcc CFLAGS = $(HIDDEN_PATHS:%=-isystem%) -Wall -Werror

在这里,$(HIDDEN_PATHS:%=-isystem%)展开的结果是-isystem/usr/include/mylibrary,即参数中每个路径前面添加了-isystem前缀。这将告诉gcc将这些路径视为系统库路径,并且不会在编译时显示它们。

通过这种方法,即使在Makefile中包含了很多路径,也能避免在编译时输出太多的信息,并且能够减少对终端的干扰。

问题:make工具如何通过一个文件来导入头文件路径?

可以通过在Makefile文件中定义变量来导入头文件路径。一种常见的做法是在一个指定目录下创建一个名为Makefile.inc(或其他任何你喜欢的名字)的文件,然后在其中定义包含路径的变量。例如,假设你的头文件存放在/usr/include/mylibrary目录下,那么你可以创建一个Makefile.inc文件,内容如下所示:

INCLUDES = -I/usr/include/mylibrary

然后在你的主Makefile中,在编译器的编译参数CFLAGS中引入该变量。例如:

include Makefile.inc CC = gcc CFLAGS = -Wall -Werror $(INCLUDES) mytarget: mysource.c $(CC) $(CFLAGS) -o mytarget mysource.c

通过上面的设置,$(INCLUDES)变量将会包含-I/usr/include/mylibrary。当你运行Makefile时,$(INCLUDES)将会被展开,将该路径添加到gcc编译器的头文件搜索路径中。

这种方法的好处是,你可以在Makefile.inc中添加或者删除头文件搜索路径,而不需要改变主Makefile文件。另外,使用Makefile.inc形式的文件,可以定义更多的变量,如编译器选项、库路径等,从而达到编译复杂工程的灵活性、规范化等目的。

问题:make在加入包含路径时可以用一个文件代替吗?而不用把所有路径都显示出来

可以使用一个文件来代替在Makefile中一个一个添加路径。这个文件通常称为.inc文件,包含了所有的包含路径。你只需要在Makefile中包含这个.inc文件,就可以将所有路径都添加到编译器的包含路径中。

举一个例子,下面这个.inc文件包含了三个路径:

INCLUDE_PATHS = \ -Ipath/to/include/file1 \ -Ipath/to/include/file2 \ -Ipath/to/include/file3

在Makefile中,可以通过下面的方式来包含这个文件:

include path/to/include_file.inc

在需要使用这些路径的地方,你可以直接使用${INCLUDE_PATHS}变量,它将会扩展为上面定义的路径列表。对于gcc和g++等编译器,可以通过CFLAGS和CXXFLAGS环境变量将其传递到编译器中,如下所示:

export CFLAGS += ${INCLUDE_PATHS} export CXXFLAGS += ${INCLUDE_PATHS}

这将会将${INCLUDE_PATHS}中包含的所有路径添加到编译器的包含路径中。

问题:OWI总线是什么?

OWI总线是单线半双工串行通信协议,其全名为One-Wire Interface,中文名为单总线接口技术。该技术由美国恩智浦半导体公司(NXP Semiconductors)开发,在一根数据线上同时实现了数据传输和供电两个功能。

OWI总线采用串行通信协议,数据传输速率通常为16.3kbps,最高可达1Mbps。由于只需要一根数据线,因此在硬件设计上非常简单,价格也比较低廉。同时,它还支持多个设备连接在同一根总线上,实现了智能化和多点控制。

应用方面,OWI总线广泛用于传感器和微控制器之间的通信,例如温度传感器、湿度传感器、晶振等。而且,由于其具有较高的可靠性和稳定性,所以在很多领域都得到了广泛的应用,如家用电器、汽车电子、医疗卫生、工业控制等等。

问题:在target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})中,如何将${dirlist})通过引用一个文件来代替?

你可以使用file()命令读取一个文件中的内容,并将其保存到一个变量中,然后在target_sources()命令中使用这个变量,示例代码如下:

# 读取存储目录列表的文件 file(READ "${CMAKE_CURRENT_SOURCE_DIR}/dirlist.txt" dirlist_file_content) # 将文件内容分割为目录列表 string(REGEX REPLACE "\n" ";" dirlist "${dirlist_file_content}") # 添加目录列表到目标文件的源代码列表中 target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})

这段代码会将${CMAKE_CURRENT_SOURCE_DIR}/dirlist.txt文件中的每一行作为一个目录,并添加到${PROJECT_NAME}.elf目标文件的源代码列表中。如果你需要对目录名称进行处理,你可以在使用string()命令和正则表达式进行处理。

问题:如何将target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})语句中的dirlist通过引用一个文件来代替?

可以使用${CMAKE_CURRENT_SOURCE_DIR}变量指代当前源码目录。

假定一个存储目录列表的文件名为dirlist.txt,该文件与CMakeLists.txt文件相同的目录中,文件中每行是一个目录名。

你可以在CMakeLists.txt文件中使用file()命令的语法来读取dirlist.txt文件中的内容:

# 读取 dirlist.txt 文件 file(STRINGS ${CMAKE_CURRENT_SOURCE_DIR}/dirlist.txt dirlist) # 将 dirlist 列表中的每个元素附加到目标文件 target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})

这段代码会将dirlist.txt文件中的每个目录以及当前源码目录(${CMAKE_CURRENT_SOURCE_DIR})中的所有源文件都添加到${PROJECT_NAME}.elf这个目标文件的源代码列表中,一起编译成可执行文件。

问题:cmake如何在target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})语句中将${dirlist}由一个txt文件替代?

可以使用file(STRINGS ...)命令读取一个文件的所有行作为一个字符串列表,并将其赋值给一个变量。然后可以将这个变量作为target_sources()命令的参数,类似如下的CMake代码:

# 读取文件内容为字符串列表 file(STRINGS "/path/to/dirlist.txt" dirlist) # 将 dirlist 列表中的每个元素附加到目标文件 target_sources(${PROJECT_NAME}.elf PRIVATE ${dirlist})

其中,file(STRINGS ...)命令读取指定文件的每一行,并将其保存为一个字符串列表,这个列表就赋值给我们的dirlist变量。

然后,我们将target_sources()命令中的${dirlist}参数替换成了刚刚读取的文件内容变量${dirlist}。

这样,CMake 就会按照 dirlist.txt 文件中的内容将所有的目录都附加到${PROJECT_NAME}.elf目标文件的源代码列表中,并在编译时将其编译到可执行文件中。

问题:cmake如何将dirlist字符串的内容保存在一个dirlist文件中?

在 CMake 中,你可以使用 file(WRITE ...) 命令来写入一个字符串到指定文件中,具体做法如下:

# 定义一个包含多个目录的字符串 set(dirlist "/path/to/dir1\n/path/to/dir2\n/path/to/dir3") # 将 dirlist 字符串的内容写入 dirlist.txt 文件中 file(WRITE "${CMAKE_CURRENT_BINARY_DIR}/dirlist.txt" "${dirlist}")

其中,set() 命令定义了一个名为 dirlist 的字符串变量,并将多个目录路径用 \n 连接起来,成为一个包含多行的字符串。

file(WRITE ...) 命令以 dirlist 变量为内容,将其写入 ${CMAKE_CURRENT_BINARY_DIR}/dirlist.txt 文件中。${CMAKE_CURRENT_BINARY_DIR} 是 CMake 的内置变量,表示 CMake 构建时生成的目标文件输出目录。

执行以上 CMake 代码后,在 ${CMAKE_CURRENT_BINARY_DIR}/dirlist.txt 文件中就保存了 dirlist 变量的内容。注意,如果该文件已经存在,file(WRITE ...) 命令将会覆盖它的原有内容。如果你想在文件末尾添加内容,可以使用类似 file(APPEND ...) 的命令。

问题:如何获取一个文件夹内包括子文件内所有c文件及路径?

在CMake中,可以使用 file(GLOB_RECURSE ...) 来获取一个文件夹内包括子文件内所有指定类型的文件及其路径。

具体做法如下:

# 获取指定文件夹及其子文件夹内所有 C 文件 file(GLOB_RECURSE C_FILES "${CMAKE_SOURCE_DIR}/path/to/folder/*.c") # 打印所有 C 文件及其路径 foreach(FILE ${C_FILES}) message("${FILE}") endforeach()

其中,${CMAKE_SOURCE_DIR} 表示 CMake 构建的源代码目录。在上面的例子中,我们假定需要获取的文件夹路径为 "path/to/folder",你需要将它替换成你实际需要获取的文件夹路径。

使用 file(GLOB_RECURSE ...) 命令可以方便地获取指定文件夹及其子文件夹内所有指定类型的文件,但需要注意的是,这种做法不推荐用于大型项目代码的管理,因为它依赖于文件系统的特定实现方式,可能会产生不可预知的结果。如果你想仅选择特定的代码文件来构建你的项目,请使用手动列举或添加指定的代码文件的方式。

问题:get_filename_component(SOURCE_ROOT_DIR ${SOURCE_ROOT_DIR_RAW} ABSOLUTE )是什么意思?

这段代码的作用是将变量 ${SOURCE_ROOT_DIR_RAW} 中保存的路径转换成绝对路径,并将结果存储到 ${SOURCE_ROOT_DIR} 变量中。

get_filename_component 命令是 CMake 内置命令之一,它可以获取一个路径的各个组成部分,例如目录部分、文件名部分、扩展名部分等。在这个例子中,使用 get_filename_component 命令获取 ${SOURCE_ROOT_DIR_RAW} 的绝对路径,并将结果存储到 ${SOURCE_ROOT_DIR} 变量中。

其中, ABSOLUTE 参数表示获取 ${SOURCE_ROOT_DIR_RAW} 的绝对路径。若 ${SOURCE_ROOT_DIR_RAW} 中保存的已是绝对路径,则此参数不起作用。

最终,${SOURCE_ROOT_DIR} 中保存的即为 ${SOURCE_ROOT_DIR_RAW} 的绝对路径。

问题:list(LENGTH dirlist result)是什么意思 ?

这段代码的作用是获取变量${dirlist}列表中元素的数量,并将结果存储到变量${result}中。list是CMake语句中的自带命令之一,LENGTH是list命令中的子命令,用于获取列表变量中元素的数量。在这个例子中,${dirlist}是要获取长度的列表变量,${result}是存储获取结果的变量。执行这个命令后,${result}变量的值即是${dirlist}列表中元素的数量。比如,如果${dirlist}中有3个元素,则 ${result} 的值为3。

问题:file(GLOB ALL_SUB RELATIVE ${root_dir} ${root_dir}/*)是什么意思?

这段代码的作用是获取指定目录 ${root_dir} 下的所有子目录和文件列表,存储到 ${ALL_SUB} 变量中,实际上是通过使用 file 命令提供的 GLOB 子命令实现的。

具体地,${root_dir}/* 用来匹配 ${root_dir} 目录下的所有文件和目录,其中 * 表示匹配任何字符,? 表示匹配单个字符。${ALL_SUB} 是匹配到的结果,是一个列表,每个元素为匹配到的相对路径。

通过设置参数为 RELATIVE ${root_dir},即可将匹配到的结果转换为相对于 ${root_dir} 目录的路径,这样方便使用与目录路径相关的 CMake 命令,例如使用 add_library 时,可以将获取到的相对路径作为参数传递给该命令。

问题:list(APPEND dirlist ${SRC_FILE})是什么意思?

这段代码的作用是将变量${SRC_FILE}指定的值添加到${dirlist}变量的末尾。list(APPEND list_name value)是一个CMake命令,它将值添加到一个列表变量中。在这个例子中,${dirlist}是要添加的列表变量,${SRC_FILE}是要添加的值。这个命令相当于C++中的dirlist.push_back(SRC_FILE)。这个命令可以用来创建和更新列表变量。

问题:macro(Add_Source_Code_Recursively root_dir)是什么意思?

这是一个宏定义,名字为Add_Source_Code_Recursively,接受一个参数root_dir。这个宏的作用是递归地向CMake工程中添加源代码。定义一个宏的主要目的是在多处使用同样的代码时,可以将代码抽象成一个宏,减少代码量并提高可读性,方便维护和修改。

问题:file(GLOB PROJECT_SOURCE_FILE ${root_dir}/.c ${root_dir}/.s ${PROJECT_SOURCE_FILE})中为什么PROJECT_SOURCE_FILE被用了两次?

PROJECT_SOURCE_FILE变量在这里用到了两次,第一次是作为通配符表达式的一部分,第二次是作为变量的名称。 file命令的语法如下:

file(GLOB output_variable [RELATIVE path] [globbing_expression]...)

其中output_variable是一个将包含匹配文件名的变量名。 在这个例子中,它的值是${PROJECT_SOURCE_FILE},这意味着每次执行这个语句都会将找到的文件添加到PROJECT_SOURCE_FILE变量中,而不是将其覆盖掉。 所以这里第二次使用PROJECT_SOURCE_FILE变量的作用是将新找到的文件添加到之前指定的文件列表中,而不是替换它们,以确保所有的源文件都能被编译。

问题:file(GLOB PROJECT_SOURCE_FILE ${root_dir}/.c ${root_dir}/.s ${PROJECT_SOURCE_FILE})是什么意思?

这段代码是使用 CMake 编译工具里的 file 命令,将 ${root_dir} 路径下所有的 .c 和 .s 文件添加到 PROJECT_SOURCE_FILE 变量中。${root_dir} 是一个变量或者一个已定义的路径,代表要搜索的文件夹路径。这段代码可以将指定文件夹下的所有 .c 和 .s 文件进行编译。

问题:有什么办法可以加快cmake建立依赖关系的速度?

CMake 建立依赖关系的速度主要受以下因素的影响:

工程规模:如果工程中有大量的源文件、目标文件和依赖库,建立依赖关系的速度就会变慢。

CMakeLists.txt 文件的复杂度:如果 CMakeLists.txt 文件包含大量的宏定义、条件语句和循环语句,建立依赖关系的时间将会增加。

编译器和处理器的速度:如果使用的计算机处理速度慢,或者使用的编译器本身处理速度慢,建立依赖关系的时间也会变长。

以下是一些优化 CMake 建立依赖关系速度的建议:

使用编译好的缓存:如果你之前已经生成过 CMake 缓存,可以重用之前的缓存来加速建立依赖关系的速度。

使用 parallel 编译:CMake 允许使用多线程来加速构建,可以使用

make -jN 命令启用 parallel 编译。其中 N 为可用的线程个数。

去除不需要的源文件:如果某些源文件已经没有被使用,可以通过从 CMakeLists.txt 文件中移除这些文件的方式减少待处理文件的数量。

指定包含目录和链接库目录:为了使 CMake 产生更少的错误,可以在 CMakeLists.txt 文件中直接指定包含目录和链接库目录,减少 CMake 查找文件的时间。

主动更新缓存:在 CMakeLists.txt 文件更新后,可以使用

cmake -B build-directory 命令来更新缓存,使 CMake 更快速地发现变化。

以上是一些常见的建议,可以对 CMake 建立依赖关系的速度产生积极的影响。

问题:cmake为何太慢?

CMake 的构建速度主要取决于以下因素:

当前工程的规模:如果工程中有大量的源文件、目标文件和依赖库,构建时间可能会很长。

CMakeLists.txt 文件的复杂度:如果 CMakeLists.txt 文件包含大量的宏定义、条件语句和循环语句,CMake 构建过程的解析和处理代码的时间将会增加。

构建环境的配置:如果构建缺少必要的库或编译器,或者使用的编译器不支持 C++11 或其他标准,CMake 生成 Makefile 的过程可能遇到困难,从而导致构建时间较长。

执行的构建类型:如果是 Debug 构建,会生成调试符号信息,会导致构建时间变长。

以下是一些优化 CMake 构建速度的建议:

将 CMake 编译出的二进制文件存储在缓存中,可以避免重复地构建依赖关系。

考虑使用 CCache 缓存编译器输出,避免重复的编译。

在编写 CMakeLists.txt 文件时,尽量保持其简单明了,避免嵌套过深的语句。

如果有多个 CPU 核心可供使用,可以使用

-j 参数来加快构建速度。

如果你是在 Windows 上进行构建,在 MSVC 编译器中启用并行编译选项(/MP)。

考虑使用预编译头 (PCH) 缓存。

总之,优化 CMake 构建速度是一个复杂的过程,需要从多个方面进行优化。以上是一些常见的优化建议,你可以根据自己的情况进行尝试。



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3